home *** CD-ROM | disk | FTP | other *** search
/ MacFormat 1995 March / macformat-022.iso / Shareware City / Graphics / SPD / Sources / libini.c < prev    next >
Encoding:
C/C++ Source or Header  |  1994-10-27  |  13.1 KB  |  482 lines  |  [TEXT/R*ch]

  1. /*
  2.  * libini.c - initialization and teardown routines.
  3.  *
  4.  * Author:  Eric Haines, 3D/Eye, Inc.
  5.  *
  6.  */
  7.  
  8. /*-----------------------------------------------------------------*/
  9. /* include section */
  10. /*-----------------------------------------------------------------*/
  11.  
  12. #include <stdio.h>
  13. #include <stdlib.h>
  14. #include <math.h>
  15. #include <string.h>
  16.  
  17. #include "lib.h"
  18. #include "drv.h"
  19.  
  20.  
  21. /*-----------------------------------------------------------------*/
  22. /* defines/constants section */
  23. /*-----------------------------------------------------------------*/
  24.  
  25.  
  26.  
  27. /*-----------------------------------------------------------------*/
  28. /* Library initialization/teardown functions */
  29. /*-----------------------------------------------------------------*/
  30. int
  31. lib_open( raytracer_format, filename )
  32. int    raytracer_format ;
  33. char    *filename ;    /* unused except for Mac version */
  34. {
  35. #ifdef OUTPUT_TO_FILE
  36.     /* no stdout, so write to a file! */
  37.     if (raytracer_format == OUTPUT_VIDEO) {
  38.     gStdout_file = stdout;
  39.     } else {
  40.     gStdout_file = fopen(filename,"w");
  41.     if ( gStdout_file == NULL ) return 1 ;
  42.     }
  43. #endif /* OUTPUT_TO_FILE */
  44.  
  45.     lib_set_output_file(gStdout_file);
  46.  
  47.     gRT_orig_format = raytracer_format;
  48.     if ((raytracer_format == OUTPUT_RTRACE) ||
  49.     (raytracer_format == OUTPUT_PLG))
  50.     lib_set_raytracer(OUTPUT_DELAYED);
  51.     else
  52.     lib_set_raytracer(raytracer_format);
  53.  
  54.     return 0 ;
  55. }
  56.  
  57. /*-----------------------------------------------------------------*/
  58. void
  59. lib_close PARAMS((void))
  60. {
  61.     /* Make sure everything is cleaned up */
  62.     if ((gRT_orig_format == OUTPUT_RTRACE) ||
  63.     (gRT_orig_format == OUTPUT_PLG)) {
  64.     lib_set_raytracer(gRT_orig_format);
  65.     lib_flush_definitions();
  66.     }
  67.  
  68.     if (gRT_out_format == OUTPUT_RIB) {
  69.     fprintf(gOutfile, "WorldEnd\n");
  70.     fprintf(gOutfile, "FrameEnd\n");
  71.     }
  72.     else if (gRT_out_format == OUTPUT_DXF) {
  73.     fprintf(gOutfile, "  0\n");
  74.     fprintf(gOutfile, "ENDSEC\n");
  75.     fprintf(gOutfile, "  0\n");
  76.     fprintf(gOutfile, "EOF\n");
  77.     }
  78.  
  79. #ifdef OUTPUT_TO_FILE
  80.     /* no stdout, so close our output! */
  81.     if (gStdout_file)
  82.     fclose(gStdout_file);
  83. #endif /* OUTPUT_TO_FILE */
  84.     if (gRT_out_format == OUTPUT_VIDEO)
  85.     display_close(1);
  86. }
  87.  
  88.  
  89. /*-----------------------------------------------------------------*/
  90. void lib_storage_initialize PARAMS((void))
  91. {
  92.     gPoly_vbuffer = (unsigned int*)malloc(VBUFFER_SIZE * sizeof(unsigned int));
  93.     gPoly_end = (int*)malloc(POLYEND_SIZE * sizeof(int));
  94.     if (!gPoly_vbuffer || !gPoly_end) {
  95.     fprintf(stderr,
  96.         "Error(lib_storage_initialize): Can't allocate memory.\n");
  97.     exit(1);
  98.     }
  99. } /* lib_storage_initialize */
  100.  
  101.  
  102. /*-----------------------------------------------------------------*/
  103. void
  104. lib_storage_shutdown PARAMS((void))
  105. {
  106.     if (gPoly_vbuffer) {
  107.     free(gPoly_vbuffer);
  108.     gPoly_vbuffer = NULL;
  109.     }
  110.     if (gPoly_end) {
  111.     free(gPoly_end);
  112.     gPoly_end = NULL;
  113.     }
  114. } /* lib_storage_shutdown */
  115.  
  116.  
  117. /*-----------------------------------------------------------------*/
  118. void show_gen_usage PARAMS((void))
  119. {
  120.     /* localize the usage strings to be expanded only once for space savings */
  121. #if defined(applec) || defined(THINK_C)
  122.     /* and don't write to stdout on Macs, which don't have console I/O, and  */
  123.     /* won't ever get this error anyway, since parms are auto-generated.     */
  124. #else
  125.  
  126.     fprintf(stderr, "usage [-s size] [-r format] [-c|t]\n");
  127.     fprintf(stderr, "-s size - input size of database\n");
  128.     fprintf(stderr, "-r format - input database format to output:\n");
  129.     fprintf(stderr, "    0   Output direct to the screen (sys dependent)\n");
  130.     fprintf(stderr, "    1   NFF - MTV\n");
  131.     fprintf(stderr, "    2   POV-Ray 1.0\n");
  132.     fprintf(stderr, "    3   Polyray v1.4, v1.5\n");
  133.     fprintf(stderr, "    4   Vivid 2.0\n");
  134.     fprintf(stderr, "    5   QRT 1.5\n");
  135.     fprintf(stderr, "    6   Rayshade\n");
  136.     fprintf(stderr, "    7   POV-Ray 2.0 (format is subject to change)\n");
  137.     fprintf(stderr, "    8   RTrace 8.0.0\n");
  138.     fprintf(stderr, "    9   PLG format for use with rend386\n");
  139.     fprintf(stderr, "    10  Raw triangle output\n");
  140.     fprintf(stderr, "    11  art 2.3\n");
  141.     fprintf(stderr, "    12  RenderMan RIB format\n");
  142.     fprintf(stderr, "    13  Autodesk DXF format (polygons only)\n");
  143.     fprintf(stderr, "    14  Wavefront OBJ format (polygons only)\n");
  144.     fprintf(stderr, "-c - output true curved descriptions\n");
  145.     fprintf(stderr, "-t - output tessellated triangle descriptions\n");
  146.  
  147. #endif
  148. } /* show_gen_usage */
  149.  
  150. void show_read_usage PARAMS((void))
  151. {
  152.     /* localize the usage strings to be expanded only once for space savings */
  153. #if defined(applec) || defined(THINK_C)
  154.     /* and don't write to stdout on Macs, which don't have console I/O, and  */
  155.     /* won't ever get this error anyway, since parms are auto-generated.     */
  156. #else
  157.  
  158.     fprintf(stderr, "usage [-f filename] [-r format] [-c|t]\n");
  159.     fprintf(stderr, "-f filename - file to import/convert/display\n");
  160.     fprintf(stderr, "-r format - format to output:\n");
  161.     fprintf(stderr, "    0   Output direct to the screen (sys dependent)\n");
  162.     fprintf(stderr, "    1   NFF - MTV\n");
  163.     fprintf(stderr, "    2   POV-Ray 1.0\n");
  164.     fprintf(stderr, "    3   Polyray v1.4, v1.5\n");
  165.     fprintf(stderr, "    4   Vivid 2.0\n");
  166.     fprintf(stderr, "    5   QRT 1.5\n");
  167.     fprintf(stderr, "    6   Rayshade\n");
  168.     fprintf(stderr, "    7   POV-Ray 2.0 (format is subject to change)\n");
  169.     fprintf(stderr, "    8   RTrace 8.0.0\n");
  170.     fprintf(stderr, "    9   PLG format for use with rend386\n");
  171.     fprintf(stderr, "    10  Raw triangle output\n");
  172.     fprintf(stderr, "    11  art 2.3\n");
  173.     fprintf(stderr, "    12  RenderMan RIB format\n");
  174.     fprintf(stderr, "    13  Autodesk DXF format (polygons only)\n");
  175.     fprintf(stderr, "    14  Wavefront OBJ format (polygons only)\n");
  176.     fprintf(stderr, "-c - output true curved descriptions\n");
  177.     fprintf(stderr, "-t - output tessellated triangle descriptions\n");
  178.  
  179. #endif
  180. } /* show_read_usage */
  181.  
  182.  
  183. /*-----------------------------------------------------------------*/
  184. /*
  185.  * Command line option parser for db generator
  186.  *
  187.  * -s size - input size of database (1 to N)
  188.  * -r format - input database format to output
  189.  *    0  Output direct to the screen (sys dependent)
  190.  *    1  NFF - MTV
  191.  *    2  POV-Ray 1.0
  192.  *    3  Polyray v1.4, v1.5
  193.  *    4  Vivid 2.0
  194.  *    5  QRT 1.5
  195.  *    6  Rayshade
  196.  *    7  POV-Ray 2.0 (format is subject to change)
  197.  *    8  RTrace 8.0.0
  198.  *    9  PLG format for use with "rend386"
  199.  *   10  Raw triangle output
  200.  *   11  art 2.3
  201.  *   12  RenderMan RIB format
  202.  *   13  Autodesk DXF format
  203.  *   14  Wavefront OBJ format
  204.  * -c - output true curved descriptions
  205.  * -t - output tessellated triangle descriptions
  206.  *
  207.  * TRUE returned if bad command line detected
  208.  * some of these are useless for the various routines - we're being a bit
  209.  * lazy here...
  210.  */
  211. int    lib_gen_get_opts( argc, argv, p_size, p_rdr, p_curve )
  212. int    argc ;
  213. char    *argv[] ;
  214. int    *p_size, *p_rdr, *p_curve ;
  215. {
  216. int num_arg ;
  217. int val ;
  218.  
  219.     num_arg = 0 ;
  220.  
  221.     while ( ++num_arg < argc ) {
  222.     if ( (*argv[num_arg] == '-') || (*argv[num_arg] == '/') ) {
  223.         switch( argv[num_arg][1] ) {
  224.         case 'c':    /* true curve output */
  225.             *p_curve = OUTPUT_CURVES ;
  226.             break ;
  227.         case 't':    /* tessellated curve output */
  228.             *p_curve = OUTPUT_PATCHES ;
  229.             break ;
  230.         case 'r':    /* renderer selection */
  231.             if ( ++num_arg < argc ) {
  232.             sscanf( argv[num_arg], "%d", &val ) ;
  233.             if ( val < OUTPUT_VIDEO || val >= OUTPUT_DELAYED ) {
  234.                 fprintf( stderr,
  235.                     "bad renderer value %d given\n",val);
  236.                 show_gen_usage();
  237.                 return( TRUE ) ;
  238.             }
  239.             *p_rdr = val ;
  240.             } else {
  241.             fprintf( stderr, "not enough args for -r option\n" ) ;
  242.             show_gen_usage();
  243.             return( TRUE ) ;
  244.             }
  245.             break ;
  246.         case 's':    /* size selection */
  247.             if ( ++num_arg < argc ) {
  248.             sscanf( argv[num_arg], "%d", &val ) ;
  249.             if ( val < 1 ) {
  250.                 fprintf( stderr,
  251.                     "bad size value %d given\n",val);
  252.                 show_gen_usage();
  253.                 return( TRUE ) ;
  254.             }
  255.             *p_size = val ;
  256.             } else {
  257.             fprintf( stderr, "not enough args for -s option\n" ) ;
  258.             show_gen_usage();
  259.             return( TRUE ) ;
  260.             }
  261.             break ;
  262.         default:
  263.             fprintf( stderr, "unknown argument -%c\n",
  264.                 argv[num_arg][1] ) ;
  265.             show_gen_usage();
  266.             return( TRUE ) ;
  267.         }
  268.     } else {
  269.         fprintf( stderr, "unknown argument %s\n",
  270.             argv[num_arg] ) ;
  271.         show_gen_usage();
  272.         return( TRUE ) ;
  273.     }
  274.     }
  275.     return( FALSE ) ;
  276. }
  277. /*-----------------------------------------------------------------*/
  278. /*
  279.  * Command line option parser for db reader (converter/displayer)
  280.  *
  281.  * -f filename - file to import/convert/display
  282.  * -r format - input database format to output
  283.  *    0  Output direct to the screen (sys dependent)
  284.  *    1  NFF - MTV
  285.  *    2  POV-Ray 1.0
  286.  *    3  Polyray v1.4, v1.5
  287.  *    4  Vivid 2.0
  288.  *    5  QRT 1.5
  289.  *    6  Rayshade
  290.  *    7  POV-Ray 2.0 (format is subject to change)
  291.  *    8  RTrace 8.0.0
  292.  *    9  PLG format for use with "rend386"
  293.  *   10  Raw triangle output
  294.  *   11  art 2.3
  295.  *   12  RenderMan RIB format
  296.  *   13  Autodesk DXF format
  297.  *   14  Wavefront OBJ format
  298.  * -c - output true curved descriptions
  299.  * -t - output tessellated triangle descriptions
  300.  *
  301.  * TRUE returned if bad command line detected
  302.  * some of these are useless for the various routines - we're being a bit
  303.  * lazy here...
  304.  */
  305. int    lib_read_get_opts( argc, argv, p_rdr, p_curve, p_infname )
  306. int    argc ;
  307. char    *argv[] ;
  308. int    *p_rdr, *p_curve ;
  309. char *p_infname;
  310. {
  311. int num_arg ;
  312. int val ;
  313.  
  314.     num_arg = 0 ;
  315.  
  316.     while ( ++num_arg < argc ) {
  317.     if ( (*argv[num_arg] == '-') || (*argv[num_arg] == '/') ) {
  318.         switch( argv[num_arg][1] ) {
  319.         case 'c':    /* true curve output */
  320.             *p_curve = OUTPUT_CURVES ;
  321.             break ;
  322.         case 't':    /* tessellated curve output */
  323.             *p_curve = OUTPUT_PATCHES ;
  324.             break ;
  325.         case 'f':    /* input file name */
  326.             if ( p_infname == NULL ) {
  327.             fprintf( stderr, "-f option not allowed\n" ) ;
  328.             show_read_usage();
  329.             return( TRUE ) ;
  330.             } else {
  331.             if ( ++num_arg < argc ) {
  332.                 sscanf( argv[num_arg], "%s", p_infname ) ;
  333.             } else {
  334.                 fprintf( stderr, "not enough args for -f option\n" ) ;
  335.                 show_read_usage();
  336.                 return( TRUE ) ;
  337.             }
  338.             }
  339.             break ;
  340.         case 'r':    /* renderer selection */
  341.             if ( ++num_arg < argc ) {
  342.             sscanf( argv[num_arg], "%d", &val ) ;
  343.             if ( val < OUTPUT_VIDEO || val >= OUTPUT_DELAYED ) {
  344.                 fprintf( stderr,
  345.                     "bad renderer value %d given\n",val);
  346.                 show_read_usage();
  347.                 return( TRUE ) ;
  348.             }
  349.             *p_rdr = val ;
  350.             } else {
  351.             fprintf( stderr, "not enough args for -r option\n" ) ;
  352.             show_read_usage();
  353.             return( TRUE ) ;
  354.             }
  355.             break ;
  356.         default:
  357.             fprintf( stderr, "unknown argument -%c\n",
  358.                 argv[num_arg][1] ) ;
  359.             show_read_usage();
  360.             return( TRUE ) ;
  361.         }
  362.     } else {
  363.         fprintf( stderr, "unknown argument %s\n",
  364.             argv[num_arg] ) ;
  365.         show_read_usage();
  366.         return( TRUE ) ;
  367.     }
  368.     }
  369.     return( FALSE ) ;
  370. }
  371.  
  372.  
  373. /*-----------------------------------------------------------------*/
  374. void
  375. lib_clear_database()
  376. {
  377.     surface_ptr ts1, ts2;
  378.     object_ptr to1, to2;
  379.     light_ptr tl1, tl2;
  380.  
  381.     gOutfile = stdout;
  382.     gTexture_name = NULL;
  383.     gTexture_count = 0;
  384.     gTexture_ior = 1.0;
  385.     gRT_out_format = OUTPUT_POVRAY_10;
  386.     gU_resolution = OUTPUT_RESOLUTION;
  387.     gV_resolution = OUTPUT_RESOLUTION;
  388.     SET_COORD3(gBkgnd_color, 0.0, 0.0, 0.0);
  389.     SET_COORD3(gFgnd_color, 0.0, 0.0, 0.0);
  390.  
  391.     /* Remove all surfaces */
  392.     ts1 = gLib_surfaces;
  393.     while (ts1 != NULL) {
  394.     ts2 = ts1;
  395.     ts1 = ts1->next;
  396.     free(ts2->surf_name);
  397.     free(ts2);
  398.     }
  399.     gLib_surfaces = NULL;
  400.  
  401.     /* Remove all objects */
  402.     to1 = gLib_objects;
  403.     while (to1 != NULL) {
  404.     to2 = to1;
  405.     to1 = to1->next_object;
  406.     free(to2);
  407.     }
  408.     gLib_objects = NULL;
  409.  
  410.     /* Remove all lights */
  411.     tl1 = gLib_lights;
  412.     while (tl1 != NULL) {
  413.     tl2 = tl1;
  414.     tl1 = tl1->next;
  415.     free(tl2);
  416.     }
  417.     gLib_lights = NULL;
  418.  
  419.     /* Reset the view */
  420.  
  421.     /* Deallocate polygon buffer */
  422.     if (gPoly_vbuffer != NULL)
  423.     lib_storage_shutdown();
  424.  
  425.     /* Clear vertex counters for polygons */
  426.     gVertex_count = 0; /* Vertex coordinates */
  427.     gNormal_count = 0; /* Vertex normals */
  428.  
  429.     /* Clear out the polygon stack */
  430.     to1 = gPolygon_stack;
  431.     while (to1 != NULL) {
  432.     to2 = to1;
  433.     to1 = to1->next_object;
  434.     free(to2);
  435.     }
  436.     gPolygon_stack = NULL;
  437. }
  438.  
  439. /*-----------------------------------------------------------------*/
  440. void
  441. lib_flush_definitions()
  442. {
  443.     switch (gRT_out_format) {
  444.        case OUTPUT_RTRACE:
  445.        case OUTPUT_VIDEO:
  446.        case OUTPUT_NFF:
  447.        case OUTPUT_POVRAY_10:
  448.        case OUTPUT_POLYRAY:
  449.        case OUTPUT_VIVID:
  450.        case OUTPUT_QRT:
  451.        case OUTPUT_RAYSHADE:
  452.        case OUTPUT_POVRAY_20:
  453.        case OUTPUT_PLG:
  454.        case OUTPUT_OBJ:
  455.        case OUTPUT_RAWTRI:
  456.         lib_output_viewpoint(gViewpoint.from, gViewpoint.at, gViewpoint.up, gViewpoint.angle,
  457.             gViewpoint.aspect, gViewpoint.hither, gViewpoint.resx, gViewpoint.resy);
  458.  
  459.         lib_output_background_color(gBkgnd_color);
  460.  
  461.         dump_all_lights();
  462.  
  463.         dump_reorder_surfaces();
  464.  
  465.         dump_all_surfaces();
  466.  
  467.         dump_all_objects();
  468.  
  469.         if (gRT_out_format == OUTPUT_RTRACE)
  470.         fprintf(gOutfile, "Textures\n\n");
  471.  
  472.         break;
  473.        case OUTPUT_DELAYED:
  474.         fprintf(stderr, "Error: Renderer not selected before flushing\n");
  475.         exit(1);
  476.     }
  477.  
  478.     if (gRT_out_format == OUTPUT_PLG)
  479.     /* An extra step is needed to build the polygon file. */
  480.     dump_plg_file();
  481. }
  482.